#include <QApplication>
#include <QAudioOutput>
#include <QWidget>
#include <QPushButton>
#include <QSlider>
#include <QListView>
#include <QLabel>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QFileDialog>
#include <QMediaPlayer>
#include <QDir>
#include <QStringListModel>
#include <QMessageBox>
#include <QTime>
#include <QFileInfo>
#include <QDebug>


class MusicPlayer : public QWidget
{
    Q_OBJECT

public:
    MusicPlayer(QWidget *parent = nullptr) : QWidget(parent)
    {
        setWindowTitle("Simple Music Player (Qt6)");
        resize(400, 300);

        // 创建 UI 元素
        playButton = new QPushButton("Play", this);
        pauseButton = new QPushButton("Pause", this);
        stopButton = new QPushButton("Stop", this);
        nextButton = new QPushButton("Next", this);
        previousButton = new QPushButton("Previous", this);

        slider = new QSlider(Qt::Horizontal, this);
        slider->setRange(0, 100);

        timeLabel = new QLabel("00:00 / 00:00", this);
        songInfoLabel = new QLabel("No song selected", this);

        // 创建音频输出设备
        audio = new QAudioOutput(this);
        audio->setVolume(1.0);  // 音量 0.0 ~ 1.0

        // 创建媒体播放器并连接音频输出
        player = new QMediaPlayer(this);
        player->setAudioOutput(audio);

        // 倍速播放控件
        speedSlider = new QSlider(Qt::Horizontal, this);
        speedSlider->setRange(50, 200);  // 代表 0.5x 到 2.0x（使用百分比）
        speedSlider->setValue(100);      // 默认 1.0x

        speedLabel = new QLabel("Speed: 1.0x", this);

        // 倍速滑块与播放器连接
        connect(speedSlider, &QSlider::valueChanged, this, [=](int value) {
            double rate = value / 100.0;
            player->setPlaybackRate(rate);
            speedLabel->setText(QString("Speed: %1x").arg(rate, 0, 'f', 1));
        });

        // 信号连接
        connect(playButton, &QPushButton::clicked, player, &QMediaPlayer::play);
        connect(pauseButton, &QPushButton::clicked, player, &QMediaPlayer::pause);
        connect(stopButton, &QPushButton::clicked, player, &QMediaPlayer::stop);
        connect(nextButton, &QPushButton::clicked, this, &MusicPlayer::playNext);
        connect(previousButton, &QPushButton::clicked, this, &MusicPlayer::playPrevious);

        connect(player, &QMediaPlayer::durationChanged, this, &MusicPlayer::onDurationChanged);
        connect(player, &QMediaPlayer::positionChanged, this, &MusicPlayer::onPositionChanged);
        connect(slider, &QSlider::sliderMoved, player, &QMediaPlayer::setPosition);

        connect(player, &QMediaPlayer::mediaStatusChanged, this, &MusicPlayer::onMediaStatusChanged);

        // 歌曲列表视图
        songListModel = new QStringListModel(this);
        songListView = new QListView(this);
        songListView->setModel(songListModel);
        songListView->setEditTriggers(QAbstractItemView::NoEditTriggers);
        connect(songListView, &QListView::clicked, this, &MusicPlayer::onSongListViewClicked);

        // 布局
        QVBoxLayout *mainLayout = new QVBoxLayout(this);

        QHBoxLayout *buttonLayout = new QHBoxLayout();
        buttonLayout->addWidget(previousButton);
        buttonLayout->addWidget(playButton);
        buttonLayout->addWidget(pauseButton);
        buttonLayout->addWidget(stopButton);
        buttonLayout->addWidget(nextButton);

        QHBoxLayout *timeLayout = new QHBoxLayout();
        timeLayout->addWidget(timeLabel);

        mainLayout->addWidget(songListView);
        mainLayout->addWidget(songInfoLabel);
        mainLayout->addLayout(buttonLayout);
        mainLayout->addWidget(slider);
        mainLayout->addLayout(timeLayout);

        QHBoxLayout *speedLayout = new QHBoxLayout();
        speedLayout->addWidget(speedLabel);
        speedLayout->addWidget(speedSlider);

        mainLayout->addLayout(speedLayout);

        // 加载本地音乐目录的歌曲
        QDir dir(QCoreApplication::applicationDirPath());
        qDebug() << "程序运行目录:" << dir.absolutePath();

        // 输出当前目录下的所有文件和文件夹
        QStringList entries = dir.entryList(QDir::AllEntries | QDir::NoDotAndDotDot);
        qDebug() << "当前目录内容:";
        for (const QString &entry : entries) {
            qDebug() << " - " << entry;
        }

        // 切换到 Music 目录
        if (!dir.cd("Music")) {
            QMessageBox::warning(this, "提示", "未找到 Music 目录，音乐无法加载。");
            qDebug() << "Music 目录不存在。";
            return;
        }

        qDebug() << "进入 Music 目录:" << dir.absolutePath();

        // 列出 Music 目录下的音频文件
        QStringList songs = dir.entryList(QStringList() << "*.mp3" << "*.wav", QDir::Files);
        if (songs.isEmpty()) {
            QMessageBox::information(this, "提示", "Music 文件夹下没有找到任何音频文件（*.mp3, *.wav）");
            qDebug() << "未找到音频文件。";
            return;
        }

        qDebug() << "找到音频文件:";
        for (const QString &file : songs) {
            qDebug() << " - " << file;
            QString path = dir.filePath(file);
            songPaths << path;
            songListModel->insertRow(songListModel->rowCount());
            QModelIndex index = songListModel->index(songListModel->rowCount() - 1);
            songListModel->setData(index, file);
        }

        if (!songPaths.isEmpty()) {
            currentIndex = 0;
            loadAndPlay(currentIndex);
        }
    }

private slots:
    void onDurationChanged(qint64 duration)
    {
        slider->setMaximum(duration);
        updateTimeLabel(duration, player->position());
    }

    void onPositionChanged(qint64 position)
    {
        slider->setValue(position);
        updateTimeLabel(player->duration(), position);
    }

    void onMediaStatusChanged(QMediaPlayer::MediaStatus status)
    {
        if (status == QMediaPlayer::EndOfMedia) {
            playNext();
        }
    }

    void onSongListViewClicked(const QModelIndex &index)
    {
        currentIndex = index.row();
        loadAndPlay(currentIndex);
    }

    void playNext()
    {
        if (songPaths.isEmpty()) return;
        currentIndex = (currentIndex + 1) % songPaths.size();
        loadAndPlay(currentIndex);
    }

    void playPrevious()
    {
        if (songPaths.isEmpty()) return;
        currentIndex = (currentIndex - 1 + songPaths.size()) % songPaths.size();
        loadAndPlay(currentIndex);
    }

private:
    void loadAndPlay(int index)
    {
        if (index < 0 || index >= songPaths.size()) return;
        player->setSource(QUrl::fromLocalFile(songPaths[index]));
        player->play();
        QString fileName = QFileInfo(songPaths[index]).fileName();
        songInfoLabel->setText("Now playing: " + fileName);
    }

    void updateTimeLabel(qint64 total, qint64 current)
    {
        auto formatTime = [](qint64 ms) {
            int secs = ms / 1000;
            int mins = secs / 60;
            secs = secs % 60;
            return QString("%1:%2").arg(mins, 2, 10, QChar('0')).arg(secs, 2, 10, QChar('0'));
        };
        timeLabel->setText(formatTime(current) + " / " + formatTime(total));
    }

    QMediaPlayer *player;
    QAudioOutput *audio;
    QStringList songPaths;
    int currentIndex = 0;

    QPushButton *playButton;
    QPushButton *pauseButton;
    QPushButton *stopButton;
    QPushButton *nextButton;
    QPushButton *previousButton;
    QSlider *slider;
    QListView *songListView;
    QLabel *timeLabel;
    QLabel *songInfoLabel;
    QStringListModel *songListModel;

    QSlider *speedSlider;
    QLabel *speedLabel;

};

#include "main.moc"


int main(int argc, char *argv[])
{
    QApplication app(argc, argv);
    MusicPlayer player;
    player.show();
    return app.exec();
}
